package com.linln.admin.config;

import org.springframework.beans.factory.annotation.Value;

import javax.crypto.BadPaddingException;
import javax.crypto.Cipher;
import javax.crypto.IllegalBlockSizeException;
import javax.crypto.NoSuchPaddingException;
import javax.crypto.spec.IvParameterSpec;
import javax.crypto.spec.SecretKeySpec;
import java.nio.charset.StandardCharsets;
import java.security.InvalidAlgorithmParameterException;
import java.security.InvalidKeyException;
import java.security.NoSuchAlgorithmException;

public class IDCardEncryptor {

    private static String APP_OPEN_KEY = "bkhRkcK3ZhTYhsu1";

    private static final String IV_STRING = "zEXaPrpd67fPrkMr";


    public static String aesEncrypt(String content) throws Exception {
        byte[] keyBytes = APP_OPEN_KEY.getBytes(StandardCharsets.UTF_8);
        SecretKeySpec skeySpec = new SecretKeySpec(keyBytes, "AES");

        byte[] ivBytes = IV_STRING.getBytes(StandardCharsets.UTF_8);
        IvParameterSpec iv = new IvParameterSpec(ivBytes);

        Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
        cipher.init(Cipher.ENCRYPT_MODE, skeySpec, iv);

        byte[] encrypted = cipher.doFinal(content.getBytes(StandardCharsets.UTF_8));
        return bytesToHex(encrypted);
    }


    /**
     * 解密
     * @param content
     * @return
     * @throws Exception
     */
    public static String aesDecrypt(String content) {

        if(content == null){
            return content;
        }
        try {
            byte[] keyBytes = APP_OPEN_KEY.getBytes(StandardCharsets.UTF_8);
            SecretKeySpec skeySpec = new SecretKeySpec(keyBytes, "AES");
            byte[] ivBytes = IV_STRING.getBytes(StandardCharsets.UTF_8);
            IvParameterSpec iv = new IvParameterSpec(ivBytes);
            Cipher cipher = null;
            cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
            cipher.init(Cipher.DECRYPT_MODE, skeySpec, iv);
            byte[] encryptedBytes = hexToBytes(content);
            byte[] original = cipher.doFinal(encryptedBytes);
            return new String(original, StandardCharsets.UTF_8);
        } catch (Exception e) {
           return content;
        }
    }

    /**
     * 脱敏展示
     * @param content
     * @return
     * @throws Exception
     */
    public static String aesTuoMinDecrypt(String content){

        if(content == null){
            return content;
        }
        try {
            byte[] keyBytes = APP_OPEN_KEY.getBytes(StandardCharsets.UTF_8);
            SecretKeySpec skeySpec = new SecretKeySpec(keyBytes, "AES");
            byte[] ivBytes = IV_STRING.getBytes(StandardCharsets.UTF_8);
            IvParameterSpec iv = new IvParameterSpec(ivBytes);
            Cipher cipher = null;
            cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
            cipher.init(Cipher.DECRYPT_MODE, skeySpec, iv);
            byte[] encryptedBytes = hexToBytes(content);
            byte[] original = cipher.doFinal(encryptedBytes);
            String s = new String(original, StandardCharsets.UTF_8);
            if (s.length() != 18) {
                return s;
            }
            String s1 = s.replaceAll("(\\d{6})\\d{8}(\\w{4})", "$1********$2");
            return s1;
        } catch (Exception e) {
            return  content;
        }

    }

    /**
     * 脱敏展示(手机号)
     * @param content
     * @return
     * @throws Exception
     */
    public static String aesTuoMinPhoneDecrypt(String content){

        if(content == null){
            return content;
        }
        try {
            byte[] keyBytes = APP_OPEN_KEY.getBytes(StandardCharsets.UTF_8);
            SecretKeySpec skeySpec = new SecretKeySpec(keyBytes, "AES");
            byte[] ivBytes = IV_STRING.getBytes(StandardCharsets.UTF_8);
            IvParameterSpec iv = new IvParameterSpec(ivBytes);
            Cipher cipher = null;
            cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
            cipher.init(Cipher.DECRYPT_MODE, skeySpec, iv);
            byte[] encryptedBytes = hexToBytes(content);
            byte[] original = cipher.doFinal(encryptedBytes);
            String s = new String(original, StandardCharsets.UTF_8);
            if (s.length() != 11) {
                return s;
            }
            return s.replaceAll("(\\d{3})\\d{4}(\\d{4})", "$1****$2");
        } catch (Exception e) {
            return content;
        }

    }


    private static String bytesToHex(byte[] bytes) {
        StringBuilder sb = new StringBuilder();
        for (byte b : bytes) {
            String hex = Integer.toHexString(b & 0xFF);
            if (hex.length() == 1) {
                hex = '0' + hex;
            }
            sb.append(hex.toUpperCase());
        }
        return sb.toString();
    }

    private static byte[] hexToBytes(String hexString) {
        if (hexString.length() % 2 != 0) {
            throw new IllegalArgumentException("Hex string must have even length");
        }

        byte[] bytes = new byte[hexString.length() / 2];
        for (int i = 0; i < hexString.length(); i += 2) {
            String hex = hexString.substring(i, i + 2);
            bytes[i / 2] = (byte) Integer.parseInt(hex, 16);
        }
        return bytes;
    }
}
